﻿using System;
using System.Collections.Generic;
using System.Data;
using System.Data.SqlClient;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Transactions;
using Dapper;

namespace Common.Library.Db
{
    public class AppDBContextDapper : SqlBulkCopyExt, IAppDBContext
    {
        #region 字段
        /// <summary>
        /// 当调用 SaveChanges 之后标记被释放
        /// </summary>
        private bool isDisposed = false;

        /// <summary>
        /// 事务
        /// </summary>
        private IDbTransaction tran = null;

        /// <summary>
        /// 数据库连接对象
        /// </summary>
        private IDbConnection db = null;
        #endregion

        #region AppDBContextDapper

        /// <summary>
        /// 构造函数，初始化 数据库连接对象
        /// </summary>
        /// <param name="connectionString"></param>
        public AppDBContextDapper(string connectionString)
        {
            if (string.IsNullOrEmpty(connectionString))
            {
                throw new Exception("数据库链接字符串不能为空");
            }
            db = new SqlConnection(connectionString);
        }

        #endregion

        #region 事务
        /// <summary>
        /// 提交事务
        /// </summary>
        public void Commit()
        {
            if (this.tran != null)
            {
                this.tran.Commit();
            }
            else
            {
                throw new Exception("问题很严重");
            }
        }

        /// <summary>
        /// 开启数据库事务
        /// </summary>
        public void OpenTransaction()
        {
            if (this.tran == null) //第一次打开事务
            {
                //创建数据库事务
                this.tran = db.BeginTransaction();
            }
        }

        /// <summary>
        /// 回滚数据库事务
        /// </summary>
        public void RollbackChanges()
        {
            this.tran.Rollback();
        }
        #endregion

        #region Dapper 执行脚本
        /// <summary>
        /// 执行SQL
        /// </summary>
        /// <param name="sql"></param>
        /// <param name="parameters"></param>
        /// <returns></returns>
        public int ExecuteCommand(string sql, object param = null)
        {
            return db.Execute(sql, param, tran);
        }


        public int Insert<T>(T entity, string tableName = "")
        {
            string sql = SqlBuilder.InsertBuilder<T>(entity, tableName);
            return ExecuteCommand(sql);
        }

        /// <summary>
        /// 获取数据
        /// </summary>
        /// <typeparam name="TEntity"></typeparam>
        /// <param name="sql"></param>
        /// <param name="parameters"></param>
        /// <returns></returns>
        public IEnumerable<TEntity> Get<TEntity>(string sql, object param = null)
        {
            return db.Query<TEntity>(sql, param);
        }

        /// <summary>
        /// 操作完成释放数据库
        /// </summary>
        public void SaveChanges()
        {
            this.Dispose();
        }

        #endregion

        /// <summary>
        /// 是否被释放
        /// </summary>
        /// <returns></returns>
        public bool IsDisposed()
        {
            return isDisposed;
        }

        #region 释放数据库连接对象
        /// <summary>
        /// 释放数据库连接对象
        /// </summary>
        private void Dispose()
        {
            //释放事务
            if (this.tran != null)
            {
                this.tran.Dispose();
                this.tran = null;
            }
            //释放数据库连接对象
            if (tran != null)
            {
                db.Close();
                db.Dispose();
            }
            this.isDisposed = true;
        }

        #endregion

    }
}
